#include <iostream>
#include <thread>
#include <future>

int Add(int x, int y)
{
    std::this_thread::sleep_for(std::chrono::seconds(3));
    return x + y;
    // Add(11, 22) 执行完毕后，返回 33（11 + 22 的结果）。
    // 由于 Add 被 std::packaged_task<int(int, int)> 包装，
    // packaged_task 会自动捕获这个返回值，并将其存入共享状态（由 packaged_task 内部管理的一块内存）
}

int main()
{
    // // 这样虽能执行，但这并不是异步操作
    // std::packaged_task<int(int, int)> task(Add);
    // std::future<int> fu = task.get_future();
    // // task(11, 22);

    // // 下边两行看似不报错，其实编译会出错，因为std::packaged_task不可拷贝
    // // 并且必须传入task，而不能传入Add，因为我们想通过future得到异步结果
    // // std::async(std::launch::async, task, 11, 22);
    // // std::thread th(task, 11, 22);

    // std::cout << fu.get() << std::endl;

    // 封装指针目的就是为了使其异步执行，使其他线程内不会出现悬空指针
    auto ptask = std::make_shared<std::packaged_task<int(int, int)>>(Add);
    std::future<int> fu = ptask->get_future();

    std::thread th([ptask](){ (*ptask)(11, 22); });

    int sum = fu.get();
    std::cout << sum << std::endl;

    th.join();

    return 0;
}